package com.hc.controller;

import com.hc.bean.Result;
import com.hc.bean.ResultUtil;
import org.apache.shiro.SecurityUtils;
import org.apache.shiro.authz.annotation.Logical;
import org.apache.shiro.authz.annotation.RequiresAuthentication;
import org.apache.shiro.authz.annotation.RequiresGuest;
import org.apache.shiro.authz.annotation.RequiresPermissions;
import org.apache.shiro.authz.annotation.RequiresRoles;
import org.apache.shiro.authz.annotation.RequiresUser;
import org.apache.shiro.subject.Subject;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;


@RestController
@RequestMapping("/shiro")
public class ShiroController {
    /**
     * 需要在ShiroConfig中添加： filterChainDefinitionMap.put("/shiro/index", "anon"); // 登录，可匿名访问
     *
     * @return
     */
    @RequiresGuest //此注解可以省略
    @GetMapping(path = "/index")
    public Result index() {
        return ResultUtil.success("本次请求不需要授权");
    }

    /**
     * 代码授权
     * <p>
     * 测试步骤：先登录，成功之后，在地址栏输入这个路径再请求
     *
     * @return
     */
    @GetMapping("/fun1")
    public Result fun1() {
        Subject subject = SecurityUtils.getSubject();
        if (subject.isAuthenticated()) {
            return ResultUtil.success("已经登录成功");
        } else {
            return ResultUtil.fail(-1, "未登录");
        }
    }

    /**
     * 代码授权
     * <p>
     * 测试步骤：先登录，成功之后，在地址栏输入这个路径再请求
     *
     * @return
     */
    @RequestMapping("/fun2")
    public Result fun2() {
        Subject subject = SecurityUtils.getSubject();
        //基于角色
        if (subject.hasRole("admin")) {
            return ResultUtil.success("拥有角色admin");
        } else {
            return ResultUtil.fail("没有角色admin");
        }
    }

    /**
     * 代码授权
     * <p>
     * 测试步骤：先登录，成功之后，在地址栏输入这个路径再请求
     *
     * @return
     */
    @RequestMapping("/fun3")
    public Result fun3() {
        Subject subject = SecurityUtils.getSubject();
        //基于资源
        if (subject.isPermitted("chapter:*:*")) {
            return ResultUtil.success("拥有权限chapter:*:*");
        } else {
            return ResultUtil.fail("没拥有权限chapter:*:*");
        }
    }

    /**
     * 代码授权
     * <p>
     * 测试步骤：先登录，成功之后，在地址栏输入这个路径再请求
     *
     * @return
     */
    @RequestMapping("/fun4")
    public Result fun4() {
        Subject subject = SecurityUtils.getSubject();
        //基于资源
        if (subject.isPermitted("chapter:crud:*")) {
            return ResultUtil.success("拥有权限chapter:crud:*");
        } else {
            return ResultUtil.fail("没拥有权限chapter:crud:*");
        }
    }

    /**
     * 注解授权
     * <p>
     * 测试步骤：先登录，成功之后，在地址栏输入这个路径再请求
     * 身份认证
     *
     * @return
     */
    @GetMapping("/fun5")
    @RequiresAuthentication
    public Result fun5() {
        return ResultUtil.success("已经被认证");
    }

    /**
     * 注解授权
     * <p>
     * 测试步骤：先登录，成功之后，在地址栏输入这个路径再请求
     *
     * @return
     */
    @RequiresUser
    @RequestMapping("/fun6")
    public Result fun6() {
        return ResultUtil.success("requiresUser");
    }

    /**
     * 注解授权
     * <p>
     * 测试步骤：先登录，成功之后，在地址栏输入这个路径再请求
     * 角色认证
     * 有同时具备user角色，才能访问
     *
     * @return
     */
    @GetMapping("/fun7")
    @RequiresRoles("teacher")
    public Result fun7() {
        return ResultUtil.success("当前访问需要teacher角色");
    }

    /**
     * 注解授权
     * <p>
     * 测试步骤：先登录，成功之后，在地址栏输入这个路径再请求
     *
     * @return
     */
    @RequestMapping("/fun8")
    @RequiresRoles("admin") //基于角色
    public Result fun8() {
        return ResultUtil.success("当前访问需要admin角色");
    }

    /**
     * 注解授权
     * <p>
     * 测试步骤：先登录，成功之后，在地址栏输入这个路径再请求
     *
     * @return
     */
    @RequestMapping("/fun9")
    @RequiresRoles(value = {"admin", "user"}, logical = Logical.OR) //基于角色
    public Result fun9() {
        return ResultUtil.success("当前访问需要admin或user角色");
    }

    /**
     * 角色认证
     * 有同时具备admin,user两个角色，才能访问
     *
     * @return
     */
    @GetMapping("/fun10")
    @RequiresRoles(value = {"admin", "user"}, logical = Logical.AND)
    public Result fun10() {
        return ResultUtil.success("当前访问需要admin和user角色");
    }

    @GetMapping("/fun11")
    @RequiresPermissions(value = {"category:find:*"})
    public Result fun11() {
        return ResultUtil.success("拥有权限category:find:*");
    }

    /**
     * 注解授权
     * <p>
     * 测试步骤：先登录，成功之后，在地址栏输入这个路径再请求
     *
     * @return
     */
    @RequestMapping("/fun12")
    @RequiresPermissions("pageStandard:*:*") //基于资源
    public Result fun12() {
        return ResultUtil.success("拥有权限pageStandard:*:*");
    }

    /**
     * 权限认证
     *
     * @return
     */
    @GetMapping("/fun13")
    @RequiresPermissions(value = {"permission:get", "permission:update"}, logical = Logical.AND)
    public Result fun13() {
        return ResultUtil.success("当前访问需要权限goods:get和goods:update");
    }

}
